package cn.lg.soar.core.excel.strategy;

import com.alibaba.excel.metadata.Head;
import com.alibaba.excel.write.merge.AbstractMergeStrategy;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.util.CellRangeAddress;

import java.util.Objects;

/**
 * 多列同规则行合并策略
 * @author luguoxiang
 * @date 2021/9/25
 * 开源项目：https://gitee.com/lgx1992/lg-soar 求star！请给我star！请帮我点个star！
 */
public class SameRuleRowMergeStrategy extends AbstractMergeStrategy {

	/**
	 * 最后一行索引
	 */
	private int lastRowIndex = -1;
	/**
	 * 规则判断列
	 */
	private Integer ruleColIndex = 0;
	/**
	 * 需要做合并处理的列
	 */
	private final int[] mergeCellIndexes;

	/**
	 *
	 * @param dataLength 数据行数
	 * @param ruleColIndex 规则判断列
	 * @param mergeColIndexes 需要做合并处理的列
	 */
	public SameRuleRowMergeStrategy(int dataLength, int ruleColIndex, int... mergeColIndexes) {
		this.lastRowIndex = dataLength - 1;
		if (mergeColIndexes == null || mergeColIndexes.length == 0) {
			throw new IllegalArgumentException("mergeCellIndexes cannot be null or empty");
		}
		this.ruleColIndex = ruleColIndex;
		this.mergeCellIndexes = mergeColIndexes;
	}

	// 合并行计数
	private int count = 0;
	// 前一行值
	private String lastValue = null;

	@Override
	protected void merge(Sheet sheet, Cell cell, Head head, Integer relativeRowIndex) {
		int currentCellIndex = cell.getColumnIndex();
		if (currentCellIndex != ruleColIndex) {
			return;
		}
		if (Objects.equals(lastValue, cell.getStringCellValue())) {
			count++;
			// 是否最后一行
			if (lastRowIndex == relativeRowIndex) {
				// 是最后一行将下标偏移到下一行（为了和非最后一行合并的计算方式一致）
				relativeRowIndex += 1;
			} else {
				// 不是最后一行不做任何处理
				return;
			}
		}
		// 与前一行值不同，对前面的数据做合并
		if (count > 0) {
			for (int mergeCellIndex : mergeCellIndexes) {
				CellRangeAddress address = new CellRangeAddress(relativeRowIndex - count, relativeRowIndex, mergeCellIndex, mergeCellIndex);
				// 合并依据相同
				sheet.addMergedRegionUnsafe(address);
			}
		}
		// 更新
		lastValue = cell.getStringCellValue();
		count = 0;
	}

}


